package com.mspbots.rule.exceptions.attendance;

import cn.hutool.core.util.StrUtil;
import com.mspbots.cw.request.AttendanceDTO;
import com.mspbots.cw.request.TenantUserConfigurationDTO;
import lombok.extern.slf4j.Slf4j;
import org.jeasy.rules.annotation.Action;
import org.jeasy.rules.annotation.Condition;
import org.jeasy.rules.annotation.Fact;
import org.jeasy.rules.annotation.Rule;
import org.springframework.util.ObjectUtils;

import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.Map;

/**
 * @ClassName com.mspbots.rule.exceptions.attendance.LateWorkStart
 * @Description TODO
 * @Author Jun
 * @Date 2019/9/18 10:57
 * @Version 1.0
 **/
@Slf4j
@Rule(name = "LateWorkStart",
        description = "Dear [User], you are 15 minutes late as your scheduled starting time [Scheduled_Starting_Time],\n" +
                "If you started work already, please type \"in at [Actual_Start_time]\" to record your real start time.\n" +
                "If you are not able to work today, please type \"Off today because [Reason]\"\n" +
                "If you will be late more, please type \" In by [ETA]\n" +
                "If there is no message from you, your manager will be notified to help figure out the attendance. \n" +
                "Thanks!")
public class LateWorkStart extends AttendanceBaseRule {

    private LocalDateTime workDateTimeUTC;

    @Condition
    public boolean condition(@Fact(FACT) TenantUserConfigurationDTO tenantUserConfigurationDTO) {
        try {

            if (!setUserMapping(tenantUserConfigurationDTO.getTenantUserId())
                    || super.checkDayMessage(tenantUserConfigurationDTO.getTenantUserId())) {
                return false;
            }

            LocalTime startTime = getTodayTime("startTime");
            if (startTime == null) {
                log.debug("tenant user [{}] startTime is null [{}]",
                        tenantUserConfigurationDTO.getTenantUserId(), LocalDateTime.now());
                return false;
            }

            workDateTimeUTC = LocalDateTime.of(LocalDateTime.now().plusHours(tz).toLocalDate(), startTime).minusHours(tz);

            Integer mins = this.tenantRuleDTO.getRuleParams().get("Mins").asInt();

            /*
            if now is between X and Y ,continue
            X = startTime + mins
            Y = startTime + mins + 1h

            eg: start time is 8:00  , mins is 10m
                now is 7:23,8:08 break
                now is 9:23,10:23 break
                now is 8:12,8:50,9:02 continue
             */
            if (LocalDateTime.now().isBefore(workDateTimeUTC.plusMinutes(mins))
                    || LocalDateTime.now().isAfter(workDateTimeUTC.plusHours(1))) {
                return false;
            }

            AttendanceDTO attendanceDTO = getAttendance(Map.of("tenantId", tenantUserConfigurationDTO.getTenantId(),
                    "userId", tenantUserConfigurationDTO.getTenantUserId(), "type", "IN"));
            if (ObjectUtils.isEmpty(attendanceDTO) || !in12Hour(attendanceDTO)) {
                log.info("no attendance  {} - {}  - {}  - {}", LocalDateTime.now(), workDateTimeUTC, mins, tenantUserConfigurationDTO.getTenantUserId());

                return true;
            }

            log.info("now and work {} - {}  - {}  - {}", LocalDateTime.now(), workDateTimeUTC, mins, tenantUserConfigurationDTO.getTenantUserId());

            return false;
        } catch (Exception e) {
            e.printStackTrace();
            log.error("LateWorkStart error : [{}] ", tenantUserConfigurationDTO.getTenantUserId());
        }
        return false;
    }

    @Action
    public void action(@Fact(FACT) TenantUserConfigurationDTO tenantUserConfigurationDTO) {
        String now = LocalDateTime.now().plusHours(tz).format(DateTimeFormatter.ofPattern("MM/dd HH:mm"));
        Map<String, Object> params = new HashMap<>(16);
        params.put("USER", tenantUserMappingDTO.getFirstName());
        params.put("Mins", styleParam(this.tenantRuleDTO.getRuleParams().get("Mins").asText()));
        params.put("StartTime", styleParam(workDateTimeUTC.plusHours(tz).format(DateTimeFormatter.ofPattern("MM/dd HH:mm"))));
        params.put("TimeZone", styleParam(tzStr));
        params.put("Software_of_time_keeping", styleParam("Software_of_time_keeping"));
        String message = StrUtil.format(this.tenantRuleDTO.getTemplate(), params);

        String suffixMessage = new StringBuilder()
                .append("--")
                .append("<span style='color:#999d9c;font-size:10px;'>")
                .append(suffixUserName())
                .append("[")
                .append(now)
                .append(" ").append(tzStr)
                .append("]")
                .append("</span>").toString();

        messages.setMessage(message + "<br>" + suffixEscalation() + suffixMessage);
        messages.setBusinessType("attendance");
        insertMessage(messages);
    }


}
